from rest_framework import serializers
from . import models
from django.conf import settings


class ApiSerializers(serializers.ModelSerializer):
    project_info = serializers.SerializerMethodField(read_only=True)  # 项目表对应字段
    creator_info = serializers.SerializerMethodField(read_only=True)  # 用户表对应字段
    sql_body_info = serializers.SerializerMethodField(read_only=True)  # sql表对应字段
    sql_assert_info = serializers.SerializerMethodField(read_only=True)  # sql表对应字段
    project_db_info = serializers.SerializerMethodField(read_only=True)  # 数据库对应信息
    create_time = serializers.DateTimeField(format='%Y-%m-%d %H:%M:%S', default=None)
    update_time = serializers.DateTimeField(format='%Y-%m-%d %H:%M:%S', default=None)

    def get_project_db_info(self, obj):
        myobj = obj.project.database
        db_types = settings.MODELS_CHOICES['database']['db_type']
        db_type = [db[1] for db in db_types if db[0] == myobj.db_type][0]
        return {
            'db_type': db_type,
            'db': myobj.db_name,
            'host': myobj.db_ip,
            'port': myobj.db_port,
            'user': myobj.db_user,
            'password': myobj.db_password,
            'charset': 'utf8'
        }

    def get_project_info(self, obj):  # 获取项目表字段的对应方法
        myobj = obj.project
        return {
            'id': myobj.id,
            'name': myobj.name,
            'describe': myobj.describe,
            'token': myobj.environment.token,
            'addr_info': '{http}://{ip}:{port}/'.format(
                http=myobj.environment.env_protocol,
                ip=myobj.environment.env_ip if not myobj.environment.env_domain else myobj.environment.env_domain,
                port=myobj.environment.env_port,
            )
        }

    def get_creator_info(self, obj):  # 获取用户表字段的对应方法
        myobj = obj.creator
        return {
            'id': myobj.id,
            'name': myobj.name,
            'username': obj.creator.username,
            'status': obj.creator.status,
        }

    def get_sql_body_info(self, obj):  # 获取sql表字段的对应方法
        myobj = obj.sql_detail_body
        if not myobj:return
        database = myobj.database
        db_types = settings.MODELS_CHOICES['database']['db_type']
        db_type = [db[1] for db in db_types if db[0] == database.db_type][0]
        return {
            'id': myobj.id,
            'sql_title': myobj.sql_title,
            'sql_template': myobj.sql_template,
            'db_type': db_type,
            'db_info': {
                'db': database.db_name,
                'host': database.db_ip,
                'port': database.db_port,
                'user': database.db_user,
                'password': database.db_password,
                'charset': 'utf8'
            },
            'status': myobj.status,
        }

    def get_sql_assert_info(self, obj):  # 获取sql表字段的对应方法
        myobj = obj.sql_detail_assert
        if not myobj: return
        database = myobj.database
        db_types = settings.MODELS_CHOICES['database']['db_type']
        db_type = [db[1] for db in db_types if db[0] == database.db_type][0]
        return {
            'id': myobj.id,
            'sql_title': myobj.sql_title,
            'sql_template': myobj.sql_template,
            'db_type': db_type,
            'db_info': {
                'db': database.db_name,
                'host': database.db_ip,
                'port': database.db_port,
                'user': database.db_user,
                'password': database.db_password,
                'charset': 'utf8'
            },
            'status': myobj.status,
        }

    class Meta:
        model = models.Api
        fields = "__all__"  # 代表获取所有字段
        # depth = 1  # 以外键关系向下找1层，数字代表层数
        extra_kwargs = {
            "project": {"write_only": True},
            "creator": {"write_only": True},
            "sql_detail_body": {"write_only": True},
            "sql_detail_assert": {"write_only": True},
        }


class ApiDetailSerializers(serializers.ModelSerializer):
    api_info = serializers.SerializerMethodField(read_only=True)  # 接口表对应字段
    project_info = serializers.SerializerMethodField(read_only=True)  # 项目表对应字段
    project_db_info = serializers.SerializerMethodField(read_only=True)  # 数据库对应信息
    creator_info = serializers.SerializerMethodField(read_only=True)  # 用户表对应字段
    sql_body_info = serializers.SerializerMethodField(read_only=True)  # sql表对应字段
    sql_assert_info = serializers.SerializerMethodField(read_only=True)  # sql表对应字段

    cases_detail_info = serializers.SerializerMethodField(read_only=True)  # 用例明细数据

    create_time = serializers.DateTimeField(format='%Y-%m-%d %H:%M:%S', default=None)
    update_time = serializers.DateTimeField(format='%Y-%m-%d %H:%M:%S', default=None)

    def get_cases_detail_info(self, obj):
        myobj = obj.cases_detail.all()
        my_dict = {
            'id': '',
            'title': '',
            'sort': ''
        }
        my_list = []
        for item in myobj:
            dt = {key: getattr(item, key) for key in my_dict}
            my_list.append(dt)
        return my_list

    def get_api_info(self, obj):
        myobj = obj.api
        return {
            'id': myobj.id,
            'name': myobj.name,
            'api_type': myobj.api_type,
            'url': myobj.url,
            'sql_detail_body': myobj.sql_detail_body.id if myobj.sql_detail_body else None,
            'sql_detail_assert': myobj.sql_detail_assert.id  if myobj.sql_detail_assert else None
        }

    def get_project_info(self, obj):  # 获取项目表字段的对应方法
        myobj = obj.api.project
        return {
            'id': myobj.id,
            'name': myobj.name,
            'describe': myobj.describe,
            'token': myobj.environment.token,
            'addr_info': '{http}://{ip}:{port}/'.format(
                http=myobj.environment.env_protocol,
                ip=myobj.environment.env_ip,
                port=myobj.environment.env_port,
            )
        }

    def get_project_db_info(self, obj):
        myobj = obj.api.project.database
        db_types = settings.MODELS_CHOICES['database']['db_type']
        db_type = [db[1] for db in db_types if db[0] == myobj.db_type][0]
        return {
            'db_type': db_type,
            'db_info':{
                'db': myobj.db_name,
                'host': myobj.db_ip,
                'port': myobj.db_port,
                'user': myobj.db_user,
                'password': myobj.db_password,
                'charset': 'utf8'
            }
        }

    def get_creator_info(self, obj):  # 获取用户表字段的对应方法
        myobj = obj.creator
        return {
            'id': myobj.id,
            'name': myobj.name,
            'username': obj.creator.username,
            'status': obj.creator.status,
        }

    def get_sql_body_info(self, obj):  # 获取sql表字段的对应方法
        myobj = obj.sql_detail_body
        if not myobj: return
        database = myobj.database
        db_types = settings.MODELS_CHOICES['database']['db_type']
        db_type = [db[1] for db in db_types if db[0] == database.db_type][0]
        return {
            'id': myobj.id,
            'sql_title': myobj.sql_title,
            'sql_template': myobj.sql_template,
            'db_type': db_type,
            'db_info': {
                'db': database.db_name,
                'host': database.db_ip,
                'port': database.db_port,
                'user': database.db_user,
                'password': database.db_password,
                'charset': 'utf8'
            },
            'status': myobj.status,
        }

    def get_sql_assert_info(self, obj):  # 获取sql表字段的对应方法
        myobj = obj.sql_detail_assert
        if not myobj: return
        database = myobj.database
        db_types = settings.MODELS_CHOICES['database']['db_type']
        db_type = [db[1] for db in db_types if db[0] == database.db_type][0]
        return {
            'id': myobj.id,
            'sql_title': myobj.sql_title,
            'sql_template': myobj.sql_template,
            'db_type': db_type,
            'db_info': {
                'db': database.db_name,
                'host': database.db_ip,
                'port': database.db_port,
                'user': database.db_user,
                'password': database.db_password,
                'charset': 'utf8'
            },
            'status': myobj.status,
        }

    class Meta:
        model = models.ApiDetail
        fields = '__all__'
        # depth = 1
        extra_kwargs = {
            "api": {"write_only": True},
            "creator": {"write_only": True},
            "sql_detail_body": {"write_only": True},
            "sql_detail_assert": {"write_only": True},
        }
